package controller

import (
	"errors"
	"gitee.com/fierce_wolf/go-fox-edge-common/commEntity"
	"gitee.com/fierce_wolf/go-fox-edge-common/commRedisStatus"
	"gitee.com/fierce_wolf/go-fox-edge-common/commUtil/Map"
	"gitee.com/fierce_wolf/go-fox-edge-common/commUtil/Method"
	"gitee.com/fierce_wolf/go-fox-edge-common/commUtil/Number"
	"gitee.com/fierce_wolf/go-fox-edge-common/edgeEnv"
	"gitee.com/fierce_wolf/go-fox-edge-common/httpserver"
	"go-fox-edge-kernel-manager/repository"
	"go-fox-edge-kernel-manager/utils/PageUtils"
	"strconv"
)

type repoLocalJarFileListController struct {
}

func (e *repoLocalJarFileListController) init() {
	httpserver.Server.POST("/repository/local/jar-file/entities", e.selectEntityList)
	httpserver.Server.POST("/repository/local/jar-file/page", e.selectPageList)
	httpserver.Server.GET("/repository/local/jar-file/entity", e.queryEntity)
	httpserver.Server.POST("/repository/local/jar-file/entity", e.insertEntity)
	httpserver.Server.PUT("/repository/local/jar-file/entity", e.updateEntity)

	httpserver.Server.POST("/repository/local/jar-file/entity/delete", e.deleteEntityList)
	httpserver.Server.POST("/repository/local/jar-file/process/restart", e.restartProcess)
	httpserver.Server.POST("/repository/local/jar-file/jar-info/query", e.getJarInfo)
}

func (e *repoLocalJarFileListController) selectEntityList(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	return e.selectList(context, body, false)
}

func (e *repoLocalJarFileListController) selectPageList(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	return e.selectList(context, body, true)
}

func (e *repoLocalJarFileListController) selectList(context httpserver.Context, body map[string]interface{}, isPage bool) (interface{}, error) {
	pageNum := Map.GetInt(body, "pageNum", 1)
	pageSize := Map.GetInt(body, "pageSize", 10)

	// 简单校验参数
	if Map.HasNull(body, "pageNum", "pageSize") {
		return nil, errors.New("参数不能为空:pageNum, pageSize")
	}

	// 从仓库获得解码器的描述信息
	repoList := repository.CloudCache.ReadList("decoder")

	// 取出需要装载的数据
	loadJars, err := repository.LocalJarFileConfig.GetLoads()
	if err != nil {
		return nil, err
	}

	// 扫描文件，获得解码器的信息
	resultList, err := repository.LocalJarFileInfo.FindJarInfo(loadJars, repoList)
	if err != nil {
		return nil, err
	}

	// 分页返回
	return PageUtils.GetMapPageList(resultList, pageNum, pageSize), nil
}

func (e *repoLocalJarFileListController) queryEntity(context httpserver.Context) (interface{}, error) {
	str := context.Query("id")
	if str == "" {
		return nil, errors.New("输入的id为null")
	}

	id, err := strconv.ParseInt(str, 10, 64)
	if err != nil {
		return nil, err
	}

	exist := repository.LocalOperate.QueryEntity(Number.MakeInt64(id))
	if exist == nil {
		return nil, errors.New("实体不存在")
	}

	return commEntity.BuildMap(exist), nil
}

func (e *repoLocalJarFileListController) insertEntity(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	delete(body, "id")
	return e.insertOrUpdate(context, body)
}

func (e *repoLocalJarFileListController) updateEntity(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	return e.insertOrUpdate(context, body)
}

func (e *repoLocalJarFileListController) insertOrUpdate(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	// 提取业务参数
	fileName := Map.GetString(body, "fileName", "")
	load := Map.GetBool(body, "load", false)

	// 简单校验参数
	if Method.HasNull(fileName, load) {
		return nil, errors.New("参数不能为空: fileName, load")
	}

	return nil, repository.LocalJarFileConfig.UpdateConfig(fileName, load)
}

func (e *repoLocalJarFileListController) deleteEntityList(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	fileNames := Map.GetSlice(body, "fileName", nil)

	// 简单校验参数
	if Method.HasEmpty(fileNames) {
		return nil, errors.New("参数不能为空: fileNames")
	}

	for _, fileName := range fileNames {
		repository.LocalJarFileInfo.DeleteFile(fileName.(string))
	}

	return nil, nil
}

func (e *repoLocalJarFileListController) restartProcess(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	if edgeEnv.IsDockerEnv() {
		return nil, errors.New("运行环境为docker，该环境不支持该操作")
	}

	// 查找设备服务的业务名称：用户安装的可能是device-service或者device-graalvm
	if !commRedisStatus.IsActive("device", "device", 60*1000) {
		return nil, errors.New("Device服务尚未启动")
	}

	// 提取业务参数
	serviceType := Map.GetString(body, "serviceType", "")
	serviceName := Map.GetString(body, "serviceName", "")

	// 简单校验参数
	if Method.HasEmpty(serviceName, serviceType) {
		return nil, errors.New("参数不能为空: serviceName, serviceType")
	}

	repository.LocalAppStart.RestartProcess(serviceName, serviceType)
	return nil, nil
}

func (e *repoLocalJarFileListController) getJarInfo(context httpserver.Context, body map[string]interface{}) (interface{}, error) {
	fileName := Map.GetString(body, "fileName", "")

	// 简单校验参数
	if Method.HasEmpty(fileName) {
		return nil, errors.New("参数不能为空: fileName")
	}

	jarInfo, err := repository.LocalJarFileInfo.ReadJarFileInfo(fileName)
	if err != nil {
		return nil, err
	}

	return jarInfo, nil
}
